 package cz.uhk.ppro.controllers.skladnik;


import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Locale;
import java.util.Map;
import javax.servlet.http.HttpSession;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.ui.ModelMap;
import org.springframework.validation.BindingResult;
import org.springframework.web.bind.annotation.ModelAttribute;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.SessionAttributes;

import cz.uhk.ppro.entities.Dil;
import cz.uhk.ppro.entities.Dodavatel;
import cz.uhk.ppro.entities.KontaktniOsoba;
import cz.uhk.ppro.entities.Stitek;
import cz.uhk.ppro.form.FiltrDily;
import cz.uhk.ppro.form.Login;
import cz.uhk.ppro.form.SkladneniForm;
import cz.uhk.ppro.services.DilDbService;
import cz.uhk.ppro.services.LoginChecker;
import cz.uhk.ppro.services.StitekDbService;
import cz.uhk.ppro.validator.SkladneniValidator;

@Controller
@SessionAttributes({"katC", "nazev", "pocet"})
public class SkladnikMainController {
	Login login;
	DilDbService dilService;
	StitekDbService stitekService;
	LoginChecker loginChecker;
	SkladneniForm skladneni;
	SkladneniValidator skladneniValidator;
	
	@Autowired
	public void setSkladneniValidator(SkladneniValidator skladneniValidator) {
		this.skladneniValidator = skladneniValidator;
	}

	@Autowired
	public void setLoginChecker (LoginChecker loginChecker){
		this.loginChecker = loginChecker;
	}
	
	@Autowired
	public void setDilService (DilDbService dilService){
		this.dilService = dilService;
	}
	
	@Autowired
	public void setStitekService (StitekDbService stitekService){
		this.stitekService = stitekService;
	}
	
	@ModelAttribute("login")
	public Login getLogin() {
		return new Login();
	}
	
	@ModelAttribute("filtrDily")
	public FiltrDily getFiltrDily() {
		return new FiltrDily();
	}
	
	@ModelAttribute("skladneni")
	public SkladneniForm getSkladneni() {
		return new SkladneniForm();
	}
	
	@RequestMapping("/skladnikHome")
	public String show(Locale locale, ModelMap model, HttpSession session,  @ModelAttribute("filtrDily") FiltrDily filtrDily) {
		if (loginChecker.checkLogin(session, "Skladnik")){
			filtrDily = new FiltrDily();
			List<Dil> dily = dilService.vypis();
			List<Stitek> stitkydb = stitekService.vypis();
			List<String> stitky = new ArrayList<String>();
			stitky.add("");
			for (Stitek s: stitkydb) {
				stitky.add(s.getNazevStitku());
			}
			model.addAttribute("dily", dily);
			model.addAttribute("stitky", stitky);
			model.addAttribute("filtrDily", filtrDily);
			return "skladnikHome";
		} else {
			return "accessDenied";
		}
	}
	
	@SuppressWarnings({ "unchecked", "rawtypes" })
	@RequestMapping("/skladnikFiltrujDily")
    public String filtruj(ModelMap model, HttpSession session, @ModelAttribute("filtrDily") FiltrDily filtrDily) {
		//http://www.devx.com/java/Article/28754/1954 ten první dlouhej způsob, je pochopitelnější
		
		Map parameters = new HashMap();
		boolean firstClause = true; 
		StringBuffer queryBuf = new StringBuffer("from Dil as d");
		String stitek = filtrDily.getStitek();
		String nazev = filtrDily.getNazev();
		String katCislo = filtrDily.getKatCislo();
		List<Dil> dily;
		
		 if (stitek.compareTo("") != 0) {
		        //queryBuf.append(firstClause ? " where " : " and "); //není třeba, bude to případně vždy první	        
			 	queryBuf.append(" join d.stitky s where s.nazevStitku in :stitek");
		        parameters.put("stitek",stitek);
		        firstClause = false;
		    }    
		    if (nazev.compareTo("")!=0) {
		        queryBuf.append(firstClause ? " join d.stitky s where " : " and "); //join aby to vracelo ve stejném formátu
		        queryBuf.append("d.nazev like :nazev");
		        parameters.put("nazev","%"+nazev+"%");  // % je wildcard - *
		        firstClause = false;
		    }
		    if (katCislo.compareTo("")!=0) {
		        queryBuf.append(firstClause ? " join d.stitky s where " : " and ");
		        queryBuf.append("d.katalogoveCislo like :katCislo");
		        parameters.put("katCislo","%"+katCislo+"%");
		        firstClause = false;
		    }
		if (!firstClause){
			String query = queryBuf.toString();
			List<Object[]> dilydb = dilService.vypisKriteria(query, parameters);
			dily = new ArrayList<Dil>();
			for (Object[] o : dilydb){
				dily.add((Dil)o[0]);
			}
		} else {
			dily = dilService.vypis();
			}
		model.addAttribute("dily", dily);
		
		return "skladnikHome";
    }
	
	@RequestMapping("/naskladnit")
	public String naskladnit(Locale locale, ModelMap model, HttpSession session, 
			@ModelAttribute("skladneni") SkladneniForm skladneni, int id) {
		if (loginChecker.checkLogin(session, "Skladnik")){
			skladneni = new SkladneniForm();
			skladneni.setId(id);
			Dil d = dilService.vrat(id);
			model.addAttribute("katC", d.getKatalogoveCislo());
			model.addAttribute("nazev", d.getNazev());
			model.addAttribute("pocet", d.getPocetKusu());
			model.addAttribute("skladneni", skladneni);
			return "skladnikNaskladni";
		} else {
			return "accessDenied";
		}
	}
	
	@RequestMapping("/naskladnitAkce")
	public String naskladnitAkce(@ModelAttribute("skladneni") SkladneniForm skladneni, BindingResult result,
			Locale locale, ModelMap model, HttpSession session) {
		skladneniValidator.validate(skladneni, result);
		if (result.hasErrors()) {
			 return "skladnikNaskladni";
		 } else {
		if (loginChecker.checkLogin(session, "Skladnik")){
			Dil d = dilService.vrat(skladneni.getId());
			dilService.naskladnit(d, skladneni.getPocet(), skladneni.getCenaKc(), skladneni.getCenaEur(), skladneni.getCenaUsd());
			return "redirect:/skladnikHome";
		} else {
			return "accessDenied";
		}}
	}
	
	@RequestMapping("/vyskladnit")
	public String vyskladnit(@ModelAttribute("skladneni") SkladneniForm skladneni, Locale locale,
			ModelMap model, HttpSession session, int id) {	
		if (loginChecker.checkLogin(session, "Skladnik")){
			skladneni = new SkladneniForm();
			skladneni.setId(id);
			Dil d = dilService.vrat(id);
			model.addAttribute("katC", d.getKatalogoveCislo());
			model.addAttribute("nazev", d.getNazev());
			model.addAttribute("pocet", d.getPocetKusu());
			model.addAttribute("skladneni", skladneni);
			return "skladnikVyskladni";
		} else {
			return "accessDenied";
		}
	}
	
	@RequestMapping("/vyskladnitAkce")
	public String vyskladnitAkce(@ModelAttribute("skladneni") SkladneniForm skladneni, BindingResult result,
			Locale locale, ModelMap model, HttpSession session) {
		skladneniValidator.validate(skladneni, result);
		if (result.hasErrors()) {
			 return "skladnikVyskladni";
		 } else {
		if (loginChecker.checkLogin(session, "Skladnik")){
			Dil d = dilService.vrat(skladneni.getId());
			dilService.vyskladnit(d, skladneni.getPocet(), skladneni.getCenaKc(), skladneni.getCenaEur(), skladneni.getCenaUsd());
			return "redirect:/skladnikHome";
		} else {
			return "accessDenied";
		}}
	}
	
	@RequestMapping("/skladnikDodavatel")
	public String dodavatel(Locale locale, ModelMap model, HttpSession session, int id) {
		if (loginChecker.checkLogin(session, "Skladnik")){
			Dil d = dilService.vrat(id);
			Dodavatel dod = d.getDodavatel();
			List<KontaktniOsoba> ko = (List<KontaktniOsoba>)dod.getKontaktniOsoby();
			model.addAttribute("katC", d.getKatalogoveCislo());
			model.addAttribute("nazev", d.getNazev());
			model.addAttribute("pocet", d.getPocetKusu());
			model.addAttribute("osoby", ko);
			model.addAttribute("dodNaz", dod.getNazevFirmy());
			model.addAttribute("adresa", dod.getUlice()+dod.getCisloPopisne());
			model.addAttribute("mesto", dod.getMesto()+dod.getPsc());
			return "skladnikDodavatel";
		} else {
			return "accessDenied";
		}
	}
}
